package com.lt.schoolchat.service.impl;

import cn.hutool.core.collection.CollectionUtil;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.lt.schoolchat.common.ErrorCode;
import com.lt.schoolchat.exception.BusinessException;
import com.lt.schoolchat.model.entity.User;
import com.lt.schoolchat.model.mongo.Video;
import com.lt.schoolchat.model.vo.VideoVO;
import com.lt.schoolchat.service.CommentService;
import com.lt.schoolchat.service.SmallVideosService;
import com.lt.schoolchat.service.UserService;
import com.lt.schoolchat.utils.GreenTextScan;
import lombok.extern.slf4j.Slf4j;
import org.bson.types.ObjectId;
import org.springframework.data.domain.Sort;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * @description:
 * @author: ~Teng~
 * @date: 2023/5/17 10:46
 */
@Service
@Slf4j
public class SmallVideosServiceImpl implements SmallVideosService {
    @Resource
    private MongoTemplate mongoTemplate;
    @Resource
    private UserService userService;
    @Resource
    private GreenTextScan greenTextScan;
    @Resource
    private CommentService commentService;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void saveVideo(String videoThumbnailUrl, String videoFileUrl, String text, Long userId) {
//        try {
//            // 1. 阿里云文本审核，若含有敏感词 禁止发布
//            Map textMap = greenTextScan.greenTextScan(text);
//            if (textMap != null) {
//                String suggestion = (String) textMap.get("suggestion");
//                if ("block".equals(suggestion)) {
//                    // 含有违规内容 禁止使用该类词语
//                    //                    text = (String) textMap.get("filteredContent");
//                    String reason = (String) textMap.get("reason");
//                    throw new BusinessException(ErrorCode.OPERATION_ERROR, "添加失败，原因：" + reason);
//                }
//            }
            // 2 保存Video到MongoDB中
            Video video = new Video();
            video.setUserId(userId);
            video.setPicUrl(videoThumbnailUrl);
            video.setVideoUrl(videoFileUrl);
            video.setText(text);
            video.setCreated(System.currentTimeMillis());
            // 保存视频
            mongoTemplate.insert(video);
//        } catch (Exception e) {
//            e.printStackTrace();
//            log.error("阿里云内容安全审核异常，原因：{}", e.getMessage());
//            throw new BusinessException(ErrorCode.OPERATION_ERROR, e.getMessage());
//        }
    }

    @Override
    public void updateVideo(ObjectId id, String videoThumbnailUrl, String videoFileUrl, String text, Long userId) {
        Query query = Query.query(Criteria.where("id").is(id));
        Video video = mongoTemplate.findOne(query, Video.class);
        if (video == null) {
            throw new BusinessException(ErrorCode.NOT_FOUND_ERROR, "该视频不存在！");
        }
        try {
            // 1. 阿里云文本审核，若含有敏感词 禁止发布
            Map textMap = greenTextScan.greenTextScan(text);
            if (textMap != null) {
                String suggestion = (String) textMap.get("suggestion");
                if ("block".equals(suggestion)) {
                    // 含有违规内容 禁止使用该类词语
                    //                    text = (String) textMap.get("filteredContent");
                    String reason = (String) textMap.get("reason");
                    throw new BusinessException(ErrorCode.OPERATION_ERROR, "添加失败，原因：" + reason);
                }
            }
            // 2 保存Video到MongoDB中
            video.setUserId(userId);
            video.setPicUrl(videoThumbnailUrl);
            video.setVideoUrl(videoFileUrl);
            video.setText(text);
            // 更新视频
            mongoTemplate.save(video);
        } catch (Exception e) {
            e.printStackTrace();
            log.error("阿里云内容安全审核异常，原因：{}", e.getMessage());
            throw new BusinessException(ErrorCode.OPERATION_ERROR, e.getMessage());
        }
    }

    @Override
    public Page<VideoVO> queryVideoList(long current, long pageSize, Integer likeCount, Long userId) {
        Page<VideoVO> page = new Page<>(current, pageSize);
        // 1. 查询视频信息
        Query query;
        if (userId == null && likeCount != null) {
            query = new Query(Criteria.where("likeCount").is(likeCount)).limit((int) pageSize).skip((current - 1) * pageSize)
                    .with(Sort.by(Sort.Order.desc("created")));
        } else if (userId == null) {
            query = new Query().limit((int) pageSize).skip((current - 1) * pageSize)
                    .with(Sort.by(Sort.Order.desc("created")));
        } else {
            query = new Query(Criteria.where("userId").is(userId))
                    .limit((int) pageSize).skip((current - 1) * pageSize)
                    .with(Sort.by(Sort.Order.desc("created")));
        }
        long total = mongoTemplate.count(new Query(), Video.class);
        List<Video> videos = mongoTemplate.find(query, Video.class);
        // 2. 查询用户信息
        List<Long> userIdList = videos.stream().map(Video::getUserId).collect(Collectors.toList());
        if (CollectionUtil.isEmpty(userIdList)) {
            return page;
        }
        Map<Long, User> map = userService.findByIds(userIdList, null);
        // 3. 构建返回值信息
        List<VideoVO> videoVOList = new ArrayList<>();
        for (Video video : videos) {
            User user = map.get(video.getUserId());
            if (user != null) {
                VideoVO videoVO = VideoVO.init(user, video);
                // 判断是否已经点赞过
                boolean flag = commentService.isLike(video.getUserId(), video.getId());
                if (flag) {
                    // 已经点赞过
                    videoVO.setHasLiked(1);
                }
                videoVOList.add(videoVO);
            }
        }
        page.setRecords(videoVOList);
        page.setTotal(total);
        return page;
    }

    @Override
    public Video getVideoById(ObjectId id) {
        Query query = Query.query(Criteria.where("id").is(id));
        return mongoTemplate.findOne(query, Video.class);
    }

    @Override
    public void removeById(ObjectId id) {
        Query query = Query.query(Criteria.where("id").is(id));
        mongoTemplate.remove(query, Video.class);
    }
}
